#include <STC89C5xRC.H>

//void UART_Init() //4800bps@11.0592MHz
//{
//	PCON |= 0x80;		//使能波特率倍速位SMOD
//	SCON = 0x40;		//8位数据,可变波特率

//	TMOD &= 0x0F;		//设置定时器模式
//	TMOD |= 0x20;		//设置定时器模式

//	TL1 = 0xF4;			//设置定时初始值
//	TH1 = 0xF4;			//设置定时重载值
//	ET1 = 0;			//禁止定时器中断
//	TR1 = 1;			//定时器1开始计时
//}

/**
  * @brief 串口初始化，4800bps@11.0592MHz
  * @param  无
  * @retval 无
  */
void UART_Init()
{
    // 1、串行口控制寄存器SCON（Serial Control）和PCON（Power Control）
    
    // 1.1、PCON：电源控制寄存器 （不可位寻址）
    //      B7     B6     B5  B4     B3    B2    B1   B0
    //   |========================||======================|
    //   | SMOD | SMOD0 | - | POF || GF1 | GF0 | PD | IDL |
    //   |  1   |   0   | 0 |  0  ||  0  |  0  | 0  |  0  |
    //   |========================||======================|
    // SMOD:    波特率选择位。
    //      SMOD=1，则使串行通信方式1、2、3的波特率加倍
    //      SMOD=0，则各工作方式的波特率加倍
    // SMOD0：  帧错误检测有效控制位
    //      SMOD0=1，SCON寄存器中的SMO/FE位用于FE(帧错误检测）功能；
    //      SMOD0=0，SCON寄存器中的SMO/FE位用于SMO功能，和SM1一起指定串行口的工作方式
	PCON |= 0x80;		//使能波特率倍速位SMOD
    
    // 1.2、SCON：串行控制寄存器 （可位寻址）
    //       B7     B6    B5    B4     B3    B2    B1   B0
    //   |==========================||=====================|
    //   | SM0/FE | SM1 | SM2 | REN || TB8 | RB8 | TI | RI |
    //   |    0   |  1  |  0  |  0  ||  0  |  0  | 0  | 0  |
    //   |==========================||=====================|
    //    SM0   SM1 工作方式  功能说明                      波特率 10
    //    0     0   方式0     同步移位串行方式：移位寄存器  波特率是SYSclk/12,
    //    0     1   方式1     8位UART,波特率可变            (2^SMOD/32)×(定时器1的溢出率)
    //    1     0   方式2     9位UART                       (2^SMOD/64)×(SYSclk系统工作时钟频率)
    //    1     1   方式3     9位UART,波特率可变            (2^SMOD/32)×(定时器1的溢出率)
    // 当单片机工作在12T模式时，定时器1的溢出率= SYSclk/12/(256-TH1);
    // 当单片机工作在6T模式时， 定时器1的溢出率= SYSclk/ 6/(256-TH1);
    // REN(Receive Enable, 允许/禁止串行接收控制位)
    // TI(Transmit Interrupt, 发送中断请求标志位)
    // RI(Receive  Interrupt, 接收中断请求标志位)
	SCON = 0x40;		//8位数据,可变波特率
    
    
    // 2、设置定时器/计数器工作模式寄存器TMOD
    //       7     6    5    4      3      2    1    0
    //   |======================||======================|
    //   | GATE | C/T | M1 | M0 || GATE | C/T | M1 | M0 |
    //   |   0  |  0  | 1  | 0  ||  -   |  -  | -  | -  |
    //   |========定时器1=======||=======定时器0========|
    //    M1    MO  定时器定时器/计数器1模式选择
    //    0     0   13位定时器/计数器，兼容8048定时模式，TL1只用低5位参与分频，TH1整个8位全用。
    //    0     1   16位定时器/计数器，TL1、TH1全用
    //    1     0   8位自动重装载定时器，当溢出时将TH1存放的值自动重装入TL1.
    //    1     1   定时器/计数器1此时无效（停止计数）。
	TMOD &= 0x0F;		//设置定时器模式
	TMOD |= 0x20;		//设置定时器模式
    
    
    // 3、设置定时器1初始值
	TL1 = 0xF4;			//设置定时初始值
	TH1 = 0xF4;			//设置定时重载值
    
    
    // 4、中断允许寄存器IE和XICON
    //     B7   B6  B5    B4    B3    B2    B1    B0
    //   |===================||=======================|
    //   | EA | - | ET2 | ES || ET1 | EX1 | ET0 | EX0 |
    //   |===================||=======================|
	ET1 = 0;			//禁止定时器中断
    
    
    // 5、定时器/计数器0/1控制寄存器TCON
    //      B7   B6    B5    B4     B3    B2    B1    B0
    //   |=======================||=======================|
    //   | TF1 | TR1 | TF0 | TR0 || IE1 | IT1 | IE0 | IT0 |
    //   |=======================||=======================|
	TR1 = 1;			//定时器1开始计时
}

/**
  * @brief 串口向电脑发送字节数据
  * @param  一个字节的Byte数据
  * @retval 无
  */
void UART_SendByte(unsigned int Byte)
{
    // 串口数据缓冲器
    SBUF=Byte;
    
    // TI: 串行口1发送中断标志。
    // 串行口1以方式0发送时，每当发送完8位数据，由硬件置1；若以方式1、方式2或方式3发送时，在发送停止位的开始时置1
    // TI=1表示串行口1正在向CPU申请中断（发送中断）。
    // 值得注意的是，CPU响应发送中断请求，转向执行中断服务程序时并不将TI清零，TI必须由用户在中断服务程序中清零。
    while(TI==0);
    TI=0;
}